/*********************************************
 * Student    : Teodoro Cipresso
 * Course     : CS286
 * Professor  : Vidya Setlur
 * Assignment : Term Project (BlueTanks)
 *********************************************/
package edu.sjsu.cs286.teodoro.cipresso.sound;

import javax.microedition.media.Manager;
import javax.microedition.media.Player;
import javax.microedition.media.control.VolumeControl;

import edu.sjsu.cs286.teodoro.cipresso.sprites.IBlueTankSprite;
import edu.sjsu.cs286.teodoro.cipresso.wizard.BlueTankGameContainer;

/**
 * This class maintains reusable player instances for all the sounds used
 * throughout the game. The actual resource caching behavior is device dependent
 * and this might turn out to be a micro-optimization.
 * 
 * @author Teodoro Cipresso
 */
public class BlueTankSoundHolder implements IBlueTankSoundHolder,
		IBlueTankSprite {

	//
	private static Player blueTankCannonPlayer = null;

	//
	private static Player redTankCannonPlayer = null;

	//
	private static Player greenTankCannon = null;

	//
	private static Player yellowTankCannonPlayer = null;

	//
	private static Player gameMusicLoopPlayer = null;

	//
	private static Player tankDestroyedPlayer = null;

	//
	private static Player tankArmorDentPlayer = null;

	//
	private static Player cannonBallCollisionPlayer = null;

	/**
	 * Get tank specific cannon sound
	 * 
	 * @param tank,
	 *            tank display name constant
	 */
	public static Player getTankCannonPlayerByName(String tankName) {
		//
		if (tankName == null)
			return null;
		//
		if (tankName.equals(BLUE_TANK_NAME)) {
			return getBlueTankCannonPlayer();
		} else if (tankName.equals(RED_TANK_NAME)) {
			return getRedTankCannonPlayer();
		} else if (tankName.equals(GREEN_TANK_NAME)) {
			return getGreenTankCannon();
		} else if (tankName.equals(YELLOW_TANK_NAME)) {
			return getYellowTankCannonPlayer();
		}
		return null;
	} // getTankCannonPlayerByName()

	/**
	 * Getter for blue tank specific cannon sound
	 */
	public static Player getBlueTankCannonPlayer() {
		if (blueTankCannonPlayer == null) {
			try {
				// get media and ready it
				blueTankCannonPlayer = createWavPlayer(BLUE_TANK_CANNON_SOUND_SRC);
				// initialize player
				initializePlayer(blueTankCannonPlayer, true);
			} catch (Exception e) {
				e.printStackTrace();
			} // try
		} // if null
		return blueTankCannonPlayer;
	} // getBlueTankCannon()

	/**
	 * Getter for green tank specific cannon sound
	 */
	public static Player getGreenTankCannon() {
		if (greenTankCannon == null) {
			try {
				// get media and ready it
				greenTankCannon = createWavPlayer(GREEN_TANK_CANNON_SOUND_SRC);
				// initialize player
				initializePlayer(greenTankCannon, true);
			} catch (Exception e) {
				e.printStackTrace();
			} // try
		} // if null
		return greenTankCannon;
	} // getGreenTankCannon()

	/**
	 * Getter for red tank specific cannon sound
	 */
	public static Player getRedTankCannonPlayer() {
		if (redTankCannonPlayer == null) {
			try {
				// get media and ready it
				redTankCannonPlayer = createWavPlayer(RED_TANK_CANNON_SOUND_SRC);
				// initialize player
				initializePlayer(redTankCannonPlayer, true);
			} catch (Exception e) {
				e.printStackTrace();
			} // try
		} // if null
		return redTankCannonPlayer;
	} // getRedTankCannon()

	/**
	 * Getter for yellow tank specific cannon sound
	 */
	public static Player getYellowTankCannonPlayer() {
		if (yellowTankCannonPlayer == null) {
			try {
				// get media and ready it
				yellowTankCannonPlayer = createWavPlayer(YELLOW_TANK_CANNON_SOUND_SRC);
				// initialize player
				initializePlayer(yellowTankCannonPlayer, true);
			} catch (Exception e) {
				e.printStackTrace();
			} // try
		} // if null
		return yellowTankCannonPlayer;
	} // getYellowTankCannon()

	/**
	 * Getter for game background music loop
	 */
	public static Player getGameMusicLoopPlayer() {
		if (gameMusicLoopPlayer == null) {
			try {
				// get media and ready it
				gameMusicLoopPlayer = createWavPlayer(GAME_LOOP_SOUND_SRC);
				// initialize player
				initializePlayer(gameMusicLoopPlayer, false);
			} catch (Exception e) {
				e.printStackTrace();
			} // try
		} // if null
		return gameMusicLoopPlayer;
	} // getGameMusicLoopPlayer()

	/**
	 * Getter for tank armor impact sound
	 */
	public static Player getTankArmorDentPlayer() {
		if (tankArmorDentPlayer == null) {
			try {
				// get media and ready it
				tankArmorDentPlayer = createWavPlayer(TANK_ARMOR_DENT_SOUND_SRC);
				// initialize player
				initializePlayer(tankArmorDentPlayer, true);
			} catch (Exception e) {
				e.printStackTrace();
			} // try
		} // if null
		return tankArmorDentPlayer;
	} // getTankArmorDentPlayer()

	/**
	 * Getter for tank destroyed sound
	 */
	public static Player getTankDestroyedPlayer() {
		if (tankDestroyedPlayer == null) {
			try {
				// get media and ready it
				tankDestroyedPlayer = createWavPlayer(TANK_DESTROYED_SOUND_SRC);
				// initialize player
				initializePlayer(tankDestroyedPlayer, true);
			} catch (Exception e) {
				e.printStackTrace();
			} // try
		} // if null
		return tankDestroyedPlayer;
	} // getTankArmorDentPlayer()

	/**
	 * Getter for tank weapon impact (collision) sound
	 */
	public static Player getCannonBallCollisionPlayer() {
		if (cannonBallCollisionPlayer == null) {
			try {
				// get media and ready it
				cannonBallCollisionPlayer = createWavPlayer(CANNON_BALL_COLLISION_SOUND_SRC);
				// initialize player
				initializePlayer(cannonBallCollisionPlayer, true);
			} catch (Exception e) {
				e.printStackTrace();
			} // try
		} // if null
		return cannonBallCollisionPlayer;
	} // getTankCollisionPlayer()

	/**
	 * Method which creates a Player instance for a wav file at the given
	 * resource location
	 * 
	 * @param wavPath,
	 *            midlet relative path of the wav file resource
	 */
	public static Player createWavPlayer(String wavPath) {
		Player player = null;
		try {
			player = Manager.createPlayer(Class.class
					.getResourceAsStream(wavPath), "audio/x-wav");
		} catch (Exception e) {
			e.printStackTrace();
		}
		return player;
	} // createWavPlayer()

	/**
	 * Initialize a new player by fetching and realizing the underlying resource
	 * and setting the volume level based on game preferences.
	 * 
	 * @param player,
	 *            player to initialize
	 * @param effect,
	 *            whether the sound is an effect (not music)
	 */
	public static void initializePlayer(Player player, boolean effect) {
		try {
			// get ready to play
			player.prefetch();
			player.realize();
			// adjust volume to game setting
			VolumeControl vc = (VolumeControl) player
					.getControl("VolumeControl");
			if (effect) {
				vc.setLevel(BlueTankGameContainer.getSoundEffectVolumeLevel());
			} else {
				vc.setLevel(BlueTankGameContainer.getMusicVolumeLevel());
			}
		} catch (Exception e) {
			e.printStackTrace();
		}
	} // initializePlayer()

	/**
	 */
	public void update() {
		// not implemented
	} // update()

} // BlueTankSoundHolder()
